﻿using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Collections.Specialized;
using Xom.Attributes;
using Xom.Elements;

namespace XomSample
{
    public class Library : XomElement, ILibrary
    {
        private IList<IBook2> _books;

        /// <summary>
        /// List of all Books
        /// </summary>
        [XomBinding("book", false, false, 0, typeof(Book2))]
        public IList<IBook2> Books
        {
            get { return _books; }
            set
            {
                _books = value;
                RaisePropertyChanged("Books");
            }
        }

        public Library()
        {
            Books = new ObservableCollection<IBook2>();

            //NotifyCollectionChanged 
            INotifyCollectionChanged notifylist = _books as INotifyCollectionChanged;
            notifylist.CollectionChanged += OnCollectionChanged;
        }

        private void OnCollectionChanged(object sender, NotifyCollectionChangedEventArgs notifyCollectionChangedEventArgs)
        {
            RaiseXomCollectionChanged(this, "Books", notifyCollectionChangedEventArgs);
        }
    }

    public class Book2 : XomElement, IBook2
    {
        private string _id;
        private bool? _isAvailable;
        private int _isbn;
        private ITitle _title;
        private IList<IAuthor> _authors;
        private IList<ICharacter> _characters;

        [XomBinding("id", true, false, 0)]
        public string Id
        {
            get { return _id; }
            set
            {
                _id = value;
                RaisePropertyChanged("Id");
            }
        }

        [XomBinding("available", true, false, 1)]
        public bool? IsAvailable
        {
            get { return _isAvailable; }
            set
            {
                _isAvailable = value;
                RaisePropertyChanged("IsAvailable");
            }
        }

        [XomBinding("isbn", false, true, 10)]
        public int Isbn
        {
            get { return _isbn; }
            set
            {
                _isbn = value;
                RaisePropertyChanged("Isbn");
            }
        }

        [XomBinding("title", false, true, 20, typeof(Title))]
        public ITitle Title
        {
            get { return _title; }
            set
            {
                _title = value;
                RaisePropertyChanged("Title");
            }
        }

        [XomBinding("author", false, false, 30, typeof(Author))]
        public IList<IAuthor> Authors
        {
            get { return _authors; }
            set
            {
                _authors = value;
                RaisePropertyChanged("Authors");
            }
        }

        [XomBinding("character", false, false, 40, typeof(Character))]
        public IList<ICharacter> Characters
        {
            get { return _characters; }
            set
            {
                _characters = value;
                RaisePropertyChanged("Characters");
            }
        }

        public Book2()
        {
            Authors = new ObservableCollection<IAuthor>();
            Characters = new ObservableCollection<ICharacter>();

            //NotifyCollectionChanged 
            INotifyCollectionChanged notifylist = _authors as INotifyCollectionChanged;
            notifylist.CollectionChanged += OnAuthorCollectionChanged;

            notifylist = _characters as INotifyCollectionChanged;
            notifylist.CollectionChanged += OnCharacterCollectionChanged;
        }

        private void OnAuthorCollectionChanged(object sender, NotifyCollectionChangedEventArgs notifyCollectionChangedEventArgs)
        {
            RaiseXomCollectionChanged(this, "Authors", notifyCollectionChangedEventArgs);
        }

        private void OnCharacterCollectionChanged(object sender, NotifyCollectionChangedEventArgs notifyCollectionChangedEventArgs)
        {
            RaiseXomCollectionChanged(this, "Characters", notifyCollectionChangedEventArgs);
        }
    }

    public class Title: XomElement, ITitle
    {
        private string _name;
        private string _language;

        // no xml name is a content
        [XomBinding("", false, false, 1)]
        public string Name
        {
            get { return _name; }
            set
            {
                _name = value;
                RaisePropertyChanged("Name");
            }
        }

        [XomBinding("lang", true, false, 0)]
        public string Language
        {
            get { return _language; }
            set
            {
                _language = value;
                RaisePropertyChanged("Language");
            }
        }
    }

    public class Author : XomElement, IAuthor
    {
        private string _id;
        private string _name;
        private string _born;
        private string _dead;

        [XomBinding("id", true, false, 0)]
        public string Id
        {
            get { return _id; }
            set
            {
                _id = value;
                RaisePropertyChanged("Id");
            }
        }

        [XomBinding("name", false, true, 10)]
        public string Name
        {
            get { return _name; }
            set
            {
                _name = value;
                RaisePropertyChanged("Name");
            }
        }

        [XomBinding("born", false, true, 20)]
        public string Born
        {
            get { return _born; }
            set
            {
                _born = value;
                RaisePropertyChanged("Born");
            }
        }

        [XomBinding("dead", false, false, 30)]
        public string Dead
        {
            get { return _dead; }
            set
            {
                _dead = value;
                RaisePropertyChanged("Dead");
            }
        }
    }

    public class Character : XomElement, ICharacter
    {
        private string _id;
        private string _name;
        private string _born;
        private string _qualification;

        [XomBinding("id", true, false, 0)]
        public string Id
        {
            get { return _id; }
            set
            {
                _id = value;
                RaisePropertyChanged("Id");
            }
        }

        [XomBinding("name", false, true, 10)]
        public string Name
        {
            get { return _name; }
            set
            {
                _name = value;
                RaisePropertyChanged("Name");
            }
        }

        [XomBinding("born", false, true, 20)]
        public string Born
        {
            get { return _born; }
            set
            {
                _born = value;
                RaisePropertyChanged("Born");
            }
        }

        [XomBinding("qualification", false, true, 30)]
        public string Qualification
        {
            get { return _qualification; }
            set
            {
                _qualification = value;
                RaisePropertyChanged("Qualification");
            }
        }
    }
}
